From 8dbf63fa5d9ffd6fdc05c2c85d0a63ed5cf12fda Mon Sep 17 00:00:00 2001
From: X Ver <jlondon2007@yahoo.com>
Date: Sat, 20 Apr 2024 14:00:19 +0300
Subject: [PATCH] reworked code

---
 include/hpdf.h           |   3 +-
 include/hpdf_conf.h      |   2 +
 include/hpdf_mmgr.h      |  25 ---
 include/hpdf_types.h     |   4 +-
 src/hpdf_doc.c           |   5 +-
 src/hpdf_list.c          | 343 +++++++--------------------------------
 src/hpdf_mmgr.c          | 254 +++--------------------------
 src/hpdf_page_operator.c |   8 +-
 src/hpdf_pages.c         |   6 +-
 9 files changed, 102 insertions(+), 548 deletions(-)

diff --git a/include/hpdf.h b/include/hpdf.h
index bf1e7c5..d8ec1d6 100644
--- a/include/hpdf.h
+++ b/include/hpdf.h
@@ -1014,7 +1014,8 @@ HPDF_ExtGState_SetBlendMode  (HPDF_ExtGState   ext_gstate,
 
 HPDF_EXPORT(HPDF_REAL)
 HPDF_Page_TextWidth  (HPDF_Page    page,
-                      const char  *text);
+                      const char  *text,
+		      const char *endptr);
 
 
 HPDF_EXPORT(HPDF_UINT)
diff --git a/include/hpdf_conf.h b/include/hpdf_conf.h
index 27d1dff..6b1d75f 100644
--- a/include/hpdf_conf.h
+++ b/include/hpdf_conf.h
@@ -82,5 +82,7 @@
 
 #define G3CODES
 
+#define PRODUCER_STRING "Console Tool"
+
 #endif /* _HPDF_CONF_H */
 
diff --git a/include/hpdf_mmgr.h b/include/hpdf_mmgr.h
index d815afd..4566f02 100644
--- a/include/hpdf_mmgr.h
+++ b/include/hpdf_mmgr.h
@@ -25,49 +25,24 @@
 extern "C" {
 #endif
 
-typedef struct  _HPDF_MPool_Node_Rec  *HPDF_MPool_Node;
-
-typedef struct  _HPDF_MPool_Node_Rec {
-    HPDF_BYTE*       buf;
-    HPDF_UINT        size;
-    HPDF_UINT        used_size;
-    HPDF_MPool_Node  next_node;
-} HPDF_MPool_Node_Rec;
-
-
 typedef struct  _HPDF_MMgr_Rec  *HPDF_MMgr;
 
 typedef struct  _HPDF_MMgr_Rec {
     HPDF_Error        error;
     HPDF_Alloc_Func   alloc_fn;
     HPDF_Free_Func    free_fn;
-    HPDF_MPool_Node   mpool;
     HPDF_UINT         buf_size;
-
-#ifdef HPDF_MEM_DEBUG
-    HPDF_UINT         alloc_cnt;
-    HPDF_UINT         free_cnt;
-#endif
 } HPDF_MMgr_Rec;
 
-
-/*  HPDF_mpool_new
- *
- *  create new HPDF_mpool object. when memory allocation goes wrong,
- *  it returns NULL and error handling function will be called.
- *  if buf_size is non-zero, mmgr is configured to be using memory-pool
- */
 HPDF_MMgr
 HPDF_MMgr_New  (HPDF_Error       error,
                 HPDF_UINT        buf_size,
                 HPDF_Alloc_Func  alloc_fn,
                 HPDF_Free_Func   free_fn);
 
-
 void
 HPDF_MMgr_Free  (HPDF_MMgr  mmgr);
 
-
 void*
 HPDF_GetMem  (HPDF_MMgr  mmgr,
               HPDF_UINT  size);
diff --git a/include/hpdf_types.h b/include/hpdf_types.h
index 5a80f9d..091e3ae 100644
--- a/include/hpdf_types.h
+++ b/include/hpdf_types.h
@@ -186,8 +186,8 @@ typedef void
                                      HPDF_STATUS   detail_no,
                                      void         *user_data);
 
-typedef void*
-(HPDF_STDCALL *HPDF_Alloc_Func)  (HPDF_UINT  size);
+typedef void *
+(*HPDF_Alloc_Func)  (size_t s);
 
 
 typedef void
diff --git a/src/hpdf_doc.c b/src/hpdf_doc.c
index 6a70f3c..eb3978d 100644
--- a/src/hpdf_doc.c
+++ b/src/hpdf_doc.c
@@ -222,7 +222,6 @@ HPDF_NewDoc  (HPDF_Doc  pdf)
     char buf[HPDF_TMP_BUF_SIZ];
     char *ptr = buf;
     char *eptr = buf + HPDF_TMP_BUF_SIZ - 1;
-    const char *version;
 
     HPDF_PTRACE ((" HPDF_NewDoc\n"));
 
@@ -269,9 +268,7 @@ HPDF_NewDoc  (HPDF_Doc  pdf)
 
     pdf->cur_pages = pdf->root_pages;
 
-    ptr = (char *)HPDF_StrCpy (ptr, (const char *)"Haru Free PDF Library ", eptr);
-    version = HPDF_GetVersion ();
-    HPDF_StrCpy (ptr, version, eptr);
+    ptr = (char *)HPDF_StrCpy (ptr, (const char *)PRODUCER_STRING, eptr);
 
     if (HPDF_SetInfoAttr (pdf, HPDF_INFO_PRODUCER, buf) != HPDF_OK)
         return HPDF_CheckError (&pdf->error);
diff --git a/src/hpdf_list.c b/src/hpdf_list.c
index b90bf1b..bd54090 100644
--- a/src/hpdf_list.c
+++ b/src/hpdf_list.c
@@ -1,336 +1,117 @@
-/*
- * << Haru Free PDF Library >> -- hpdf_list.c
- *
- * URL: http://libharu.org
- *
- * Copyright (c) 1999-2006 Takeshi Kanno <takeshi_kanno@est.hi-ho.ne.jp>
- * Copyright (c) 2007-2009 Antony Dovgal <tony@daylessday.org>
- *
- * Permission to use, copy, modify, distribute and sell this software
- * and its documentation for any purpose is hereby granted without fee,
- * provided that the above copyright notice appear in all copies and
- * that both that copyright notice and this permission notice appear
- * in supporting documentation.
- * It is provided "as is" without express or implied warranty.
- *
- */
+#include <assert.h>
+#include <stdlib.h>
+
+#include <string.h>
 
 #include "hpdf_conf.h"
-#include "hpdf_utils.h"
 #include "hpdf_consts.h"
 #include "hpdf_list.h"
 
-static HPDF_STATUS
-Resize  (HPDF_List  list,
-         HPDF_UINT  count);
-
-
-/*
- *  HPDF_List_new
- *
- *  mmgr :  handle to a HPDF_MMgr object.
- *  items_per_block :  number of increases of pointers.
- *
- *  return:  If HPDF_List_New success, it returns a handle to new HPDF_List
- *           object, otherwise it returns NULL.
- *
- */
-
 HPDF_List
-HPDF_List_New  (HPDF_MMgr  mmgr,
-                HPDF_UINT  items_per_block)
+HPDF_List_New(HPDF_MMgr mmgr, HPDF_UINT items_per_block)
 {
-    HPDF_List list;
-
-    HPDF_PTRACE((" HPDF_List_New\n"));
-
-    if (mmgr == NULL)
-        return NULL;
-
-    list = (HPDF_List)HPDF_GetMem (mmgr, sizeof(HPDF_List_Rec));
-    if (list) {
-        list->mmgr = mmgr;
-        list->error = mmgr->error;
-        list->block_siz = 0;
-        list->items_per_block =
-            (items_per_block <= 0 ? HPDF_DEF_ITEMS_PER_BLOCK : items_per_block);
-        list->count = 0;
-        list->obj = NULL;
-    }
-
-    return list;
+	HPDF_List list = (HPDF_List)malloc(sizeof(HPDF_List_Rec));
+	assert(list);
+	if (items_per_block)
+		list->items_per_block = items_per_block;
+	else
+		list->items_per_block = HPDF_DEF_ITEMS_PER_BLOCK;
+	list->mmgr = mmgr;
+	list->error = mmgr->error;
+	list->block_siz = list->items_per_block;
+	list->obj = (void **)calloc(list->block_siz, sizeof(void *));
+	assert(list->obj);
+	list->count = 0;
+	return list;
 }
 
-/*
- *  HPDF_List_add
- *
- *  list :  Pointer to a HPDF_List object.
- *  item :  Pointer to a object to be added.
- *
- *  return:  If HPDF_List_Add success, it returns HPDF_OK.
- *           HPDF_FAILD_TO_ALLOC_MEM is returned when the expansion of the
- *           object list is failed.
- *
- */
+static void
+list_grow(HPDF_List in)
+{
+	in->block_siz += in->items_per_block;
+	in->obj = (void **)realloc(in->obj, sizeof(void *) * in->block_siz);
+	assert(in->obj);
+}
 
 HPDF_STATUS
-HPDF_List_Add  (HPDF_List  list,
-                void       *item)
+HPDF_List_Add(HPDF_List list, void *item)
 {
-    HPDF_PTRACE((" HPDF_List_Add\n"));
-
-    if (list->count >= list->block_siz) {
-        HPDF_STATUS ret = Resize (list,
-                list->block_siz + list->items_per_block);
-
-        if (ret != HPDF_OK) {
-            return ret;
-        }
-    }
-
-    list->obj[list->count++] = item;
-    return HPDF_OK;
+	if (list->count >= list->block_siz)
+		list_grow(list);
+	list->obj[list->count ++] = item;
+	return HPDF_OK;
 }
 
-
-/*
- *  HPDF_List_Insert
- *
- *  list   :  Pointer to a HPDF_List object.
- *  target :  Pointer to the target object.
- *  item   :  Pointer to a object to be inserted.
- *
- *  insert the item before the target.
- *
- *  return:  If HPDF_List_Add success, it returns HPDF_OK.
- *           HPDF_FAILD_TO_ALLOC_MEM is returned when the expansion of the
- *           object list is failed.
- *           HPDF_ITEM_NOT_FOUND is returned where the target object is not
- *           found.
- *
- */
-
 HPDF_STATUS
-HPDF_List_Insert  (HPDF_List  list,
-                   void       *target,
-                   void       *item)
+HPDF_List_Insert(HPDF_List list, void *target, void *item)
 {
-    HPDF_INT target_idx = HPDF_List_Find (list, target);
-    void      *last_item = list->obj[list->count - 1];
-    HPDF_INT i;
-
-    HPDF_PTRACE((" HPDF_List_Insert\n"));
-
-    if (target_idx < 0)
-        return HPDF_ITEM_NOT_FOUND;
-
-    /* move the item of the list to behind one by one. */
-    for (i = list->count - 2; i >= target_idx; i--)
-        list->obj[i + 1] = list->obj[i];
-
-    list->obj[target_idx] = item;
-
-    return HPDF_List_Add (list, last_item);
+	HPDF_INT target_idx = HPDF_List_Find(list, target);
+	if (target_idx == -1)
+		return HPDF_ITEM_NOT_FOUND;
+	if (list->count + 1 > list->block_siz)
+		list_grow(list);
+	memmove(list->obj + target_idx + 1, list->obj + target_idx,
+			sizeof(void *) * (list->count - target_idx));
+	list->obj[target_idx] = item;
+	list->count ++;
+	return HPDF_OK;
 }
 
-/*
- *  HPDF_List_Remove
- *
- *  Remove the object specified by item parameter from the list object. The
- *  memory area that the object uses is not released.
- *
- *  list :  Pointer to a HPDF_List object.
- *  item :  Pointer to a object to be remove.
- *
- *  return:  If HPDF_List_Remove success, it returns HPDF_OK.
- *           HPDF_ITEM_NOT_FOUND is returned when the object specified by item
- *           parameter is not found.
- *
- */
-
 HPDF_STATUS
-HPDF_List_Remove  (HPDF_List  list,
-                   void       *item)
+HPDF_List_Remove(HPDF_List list, void *item)
 {
-    HPDF_UINT i;
-    void **obj = list->obj;
-
-    HPDF_PTRACE((" HPDF_List_Remove\n"));
-
-    for (i = 0; i < list->count; i++) {
-        if (*obj == item) {
-            HPDF_List_RemoveByIndex(list, i);
-            return HPDF_OK;
-        } else
-            obj++;
-    }
-
-    return HPDF_ITEM_NOT_FOUND;
+	int x = HPDF_List_Find(list, item);
+	if (x == -1)
+		return HPDF_ITEM_NOT_FOUND;
+	HPDF_List_RemoveByIndex(list, x);
+	return HPDF_OK;
 }
 
-/*
- *  HPDF_List_RemoveByIndex
- *
- *  Remove the object by index number.
- *
- *  list :  Pointer to a HPDF_List object.
- *  index :  Index of a object to be remove.
- *
- *  return:  If HPDF_List_RemoveByIndex success, it returns HPDF_OK.
- *           HPDF_ITEM_NOT_FOUND is returned when the value which is specified
- *           by index parameter is invalid.
- *
- */
-
-void*
+void *
 HPDF_List_RemoveByIndex  (HPDF_List  list,
                           HPDF_UINT  index)
 {
-    void *tmp;
-
-    HPDF_PTRACE((" HPDF_List_RemoveByIndex\n"));
-
-    if (list->count <= index)
-        return NULL;
-
-    tmp = list->obj[index];
-
-    while (index < list->count - 1) {
-        list->obj[index] = list->obj[index + 1];
-        index++;
-    }
-
-    list->count--;
-
-    return tmp;
+	if (list->count <= index)
+		return NULL;
+	memmove(list->obj + index, list->obj + index + 1,
+			sizeof(void *) * (list->count - index - 1));
+	list->count --;
+	return NULL;
 }
 
-/*
- *  HPDF_List_ItemAt
- *
- *  list :  Pointer to a HPDF_List object.
- *  index :  Index of a object.
- *
- *  return:  If HPDF_List_at success, it returns a pointer to the object.
- *           otherwise it returns NULL.
- *
- */
-
-void*
-HPDF_List_ItemAt  (HPDF_List  list,
-                   HPDF_UINT  index)
+void *
+HPDF_List_ItemAt(HPDF_List list, HPDF_UINT index)
 {
-    HPDF_PTRACE((" HPDF_List_ItemAt\n"));
-
     return (list->count <= index) ? NULL : list->obj[index];
 }
 
-/*
- *  HPDF_List_free
- *
- *  list :  Pointer to a HPDF_List object.
- *
- */
-
 void
-HPDF_List_Free  (HPDF_List  list)
+HPDF_List_Free(HPDF_List list)
 {
-    HPDF_PTRACE((" HPDF_List_Free\n"));
-
     if (!list)
-        return ;
-
+        return;
     HPDF_List_Clear (list);
     HPDF_FreeMem (list->mmgr, list);
 }
 
-/*
- *  HPDF_List_Clear
- *
- *  list :  Pointer to a HPDF_List object.
- *
- */
-
 void
-HPDF_List_Clear  (HPDF_List  list)
+HPDF_List_Clear(HPDF_List list)
 {
-    HPDF_PTRACE((" HPDF_List_Clear\n"));
-
     if (list->obj)
-        HPDF_FreeMem (list->mmgr, list->obj);
-
+        HPDF_FreeMem(list->mmgr, list->obj);
     list->block_siz = 0;
     list->count = 0;
     list->obj = NULL;
 }
 
-/*
- *  Resize
- *
- *  list :  Pointer to a HPDF_List object.
- *  count : The size of array of pointers.
- *
- *  return:  If Resize success, it returns HPDF_OK.
- *           otherwise it returns error-code which is set by HPDF_MMgr object.
- *
- */
-
-static HPDF_STATUS
-Resize  (HPDF_List   list,
-         HPDF_UINT   count)
-{
-    void **new_obj;
-
-    HPDF_PTRACE((" HPDF_List_Resize\n"));
-
-    if (list->count >= count) {
-        if (list->count == count)
-            return HPDF_OK;
-        else
-            return HPDF_INVALID_PARAMETER;
-    }
-
-    new_obj = (void **)HPDF_GetMem (list->mmgr, count * sizeof(void *));
-
-    if (!new_obj)
-        return HPDF_Error_GetCode (list->error);
-
-    if (list->obj)
-        HPDF_MemCpy ((HPDF_BYTE *)new_obj, (HPDF_BYTE *)list->obj,
-                list->block_siz * sizeof(void *));
-
-    list->block_siz = count;
-    if (list->obj)
-        HPDF_FreeMem (list->mmgr, list->obj);
-    list->obj = new_obj;
-
-    return HPDF_OK;
-}
-
-/*
- *  HPDF_List_Find
- *
- *  list :  Pointer to a HPDF_List object.
- *  count : the size of array of pointers.
- *
- *  return:  If HPDF_List_Find success, it returns index of the object.
- *           otherwise it returns negative value.
- *
- */
-
 HPDF_INT32
-HPDF_List_Find  (HPDF_List  list,
-                 void       *item)
+HPDF_List_Find(HPDF_List list, void *item)
 {
     HPDF_UINT i;
-
-    HPDF_PTRACE((" HPDF_List_Find\n"));
-
-    for (i = 0; i < list->count; i++) {
+    for (i = 0; i < list->count; i ++) {
         if (list->obj[i] == item)
             return i;
     }
-
     return -1;
 }
 
diff --git a/src/hpdf_mmgr.c b/src/hpdf_mmgr.c
index 3069a05..b25c4fe 100644
--- a/src/hpdf_mmgr.c
+++ b/src/hpdf_mmgr.c
@@ -1,250 +1,46 @@
-/*
- * << Haru Free PDF Library >> -- hpdf_mmgr.c
- *
- * URL: http://libharu.org
- *
- * Copyright (c) 1999-2006 Takeshi Kanno <takeshi_kanno@est.hi-ho.ne.jp>
- * Copyright (c) 2007-2009 Antony Dovgal <tony@daylessday.org>
- *
- * Permission to use, copy, modify, distribute and sell this software
- * and its documentation for any purpose is hereby granted without fee,
- * provided that the above copyright notice appear in all copies and
- * that both that copyright notice and this permission notice appear
- * in supporting documentation.
- * It is provided "as is" without express or implied warranty.
- *
- */
-
-#include "hpdf_conf.h"
 #include "hpdf_consts.h"
 #include "hpdf_mmgr.h"
-#include "hpdf_utils.h"
-
-#ifndef HPDF_STDCALL
-#ifdef HPDF_DLL_MAKE
-#define HPDF_STDCALL __stdcall
-#else
-#ifdef HPDF_DLL
-#define HPDF_STDCALL __stdcall
-#else
-#define HPDF_STDCALL
-#endif
-#endif
-#endif
-
-static void * HPDF_STDCALL
-InternalGetMem  (HPDF_UINT  size);
-
-static void HPDF_STDCALL
-InternalFreeMem  (void*  aptr);
-
 
 HPDF_MMgr
-HPDF_MMgr_New  (HPDF_Error       error,
-                HPDF_UINT        buf_size,
-                HPDF_Alloc_Func  alloc_fn,
-                HPDF_Free_Func   free_fn)
+HPDF_MMgr_New(HPDF_Error error, HPDF_UINT buf_size, HPDF_Alloc_Func alloc_fn,
+        HPDF_Free_Func free_fn)
 {
     HPDF_MMgr mmgr;
-
-    HPDF_PTRACE((" HPDF_MMgr_New\n"));
-
-    if (alloc_fn)
-        mmgr = (HPDF_MMgr)alloc_fn (sizeof(HPDF_MMgr_Rec));
-    else
-        mmgr = (HPDF_MMgr)InternalGetMem (sizeof(HPDF_MMgr_Rec));
-
-    HPDF_PTRACE(("+%p mmgr-new\n", mmgr));
-
-    if (mmgr != NULL) {
-        /* initialize mmgr object */
-        mmgr->error = error;
-
-
-#ifdef HPDF_MEM_DEBUG
-        mmgr->alloc_cnt = 0;
-        mmgr->free_cnt = 0;
-#endif
-        /*
-         *  if alloc_fn and free_fn are specified, these function is
-         *  used. if not, default function (maybe these will be "malloc" and
-         *  "free") is used.
-         */
-        if (alloc_fn && free_fn) {
-            mmgr->alloc_fn = alloc_fn;
-            mmgr->free_fn = free_fn;
-        } else {
-            mmgr->alloc_fn = InternalGetMem;
-            mmgr->free_fn = InternalFreeMem;
-        }
-
-        /*
-         *  if buf_size parameter is specified, this object is configured
-         *  to be using memory-pool.
-         *
-         */
-        if (!buf_size)
-            mmgr->mpool = NULL;
-        else {
-            HPDF_MPool_Node node;
-
-            node = (HPDF_MPool_Node)mmgr->alloc_fn (sizeof(HPDF_MPool_Node_Rec) +
-                    buf_size);
-
-            HPDF_PTRACE(("+%p mmgr-node-new\n", node));
-
-            if (node == NULL) {
-                HPDF_SetError (error, HPDF_FAILD_TO_ALLOC_MEM, HPDF_NOERROR);
-
-                mmgr->free_fn(mmgr);
-                mmgr = NULL;
-            } else {
-                mmgr->mpool = node;
-                node->buf = (HPDF_BYTE *)node + sizeof(HPDF_MPool_Node_Rec);
-                node->size = buf_size;
-                node->used_size = 0;
-                node->next_node = NULL;
-            }
-
-#ifdef HPDF_MEM_DEBUG
-            if (mmgr) {
-                mmgr->alloc_cnt += 1;
-            }
-#endif
-        }
-
-        if (mmgr) {
-            mmgr->buf_size = buf_size;
-        }
-    } else
-        HPDF_SetError(error, HPDF_FAILD_TO_ALLOC_MEM, HPDF_NOERROR);
-
+    mmgr = malloc(sizeof(HPDF_MMgr_Rec));
+    if (!mmgr) {
+	HPDF_SetError(error, HPDF_FAILD_TO_ALLOC_MEM, HPDF_NOERROR);
+	return NULL;
+    }
+    mmgr->error = error;
+    mmgr->alloc_fn = malloc;
+    mmgr->free_fn = free;
+    mmgr->buf_size = buf_size;
     return mmgr;
+    (void)alloc_fn;
+    (void)free_fn;
 }
 
 void
-HPDF_MMgr_Free  (HPDF_MMgr  mmgr)
+HPDF_MMgr_Free(HPDF_MMgr mmgr)
 {
-    HPDF_MPool_Node node;
-
-    HPDF_PTRACE((" HPDF_MMgr_Free\n"));
-
-    if (mmgr == NULL)
-        return;
-
-    node = mmgr->mpool;
-
-    /* delete all nodes recursively */
-    while (node != NULL) {
-        HPDF_MPool_Node tmp = node;
-        node = tmp->next_node;
-
-        HPDF_PTRACE(("-%p mmgr-node-free\n", tmp));
-        mmgr->free_fn (tmp);
-
-#ifdef HPDF_MEM_DEBUG
-        mmgr->free_cnt++;
-#endif
-
-    }
-
-#ifdef HPDF_MEM_DEBUG
-    HPDF_PRINTF ("# HPDF_MMgr alloc-cnt=%u, free-cnt=%u\n",
-            mmgr->alloc_cnt, mmgr->free_cnt);
-
-    if (mmgr->alloc_cnt != mmgr->free_cnt)
-        HPDF_PRINTF ("# ERROR #\n");
-#endif
-
-    HPDF_PTRACE(("-%p mmgr-free\n", mmgr));
-    mmgr->free_fn (mmgr);
+    mmgr->free_fn(mmgr);
 }
 
-void*
-HPDF_GetMem  (HPDF_MMgr  mmgr,
-              HPDF_UINT  size)
+void *
+HPDF_GetMem(HPDF_MMgr mmgr, HPDF_UINT  size)
 {
-    void * ptr;
-
-    if (mmgr->mpool) {
-        HPDF_MPool_Node node = mmgr->mpool;
-
-#ifdef HPDF_ALINMENT_SIZ
-        size = (size + (HPDF_ALINMENT_SIZ - 1)) / HPDF_ALINMENT_SIZ;
-        size *= HPDF_ALINMENT_SIZ;
-#endif
-
-        if (node->size - node->used_size >= size) {
-            ptr = (HPDF_BYTE*)node->buf + node->used_size;
-            node->used_size += size;
-            return ptr;
-        } else {
-            HPDF_UINT tmp_buf_siz = (mmgr->buf_size < size) ?  size :
-                mmgr->buf_size;
-
-            node = (HPDF_MPool_Node)mmgr->alloc_fn (sizeof(HPDF_MPool_Node_Rec)
-                    + tmp_buf_siz);
-            HPDF_PTRACE(("+%p mmgr-new-node\n", node));
-
-            if (!node) {
-                HPDF_SetError (mmgr->error, HPDF_FAILD_TO_ALLOC_MEM,
-                        HPDF_NOERROR);
-                return NULL;
-            }
-
-            node->size = tmp_buf_siz;
-        }
-
-        node->next_node = mmgr->mpool;
-        mmgr->mpool = node;
-        node->used_size = size;
-        node->buf = (HPDF_BYTE*)node + sizeof(HPDF_MPool_Node_Rec);
-        ptr = node->buf;
-    } else {
-        ptr = mmgr->alloc_fn (size);
-        HPDF_PTRACE(("+%p mmgr-alloc_fn size=%u\n", ptr, size));
-
-        if (ptr == NULL)
-            HPDF_SetError (mmgr->error, HPDF_FAILD_TO_ALLOC_MEM, HPDF_NOERROR);
-    }
-
-#ifdef HPDF_MEM_DEBUG
-    if (ptr)
-        mmgr->alloc_cnt++;
-#endif
-
+    void *ptr;
+    ptr = mmgr->alloc_fn (size);
+    if (ptr == NULL)
+        HPDF_SetError(mmgr->error, HPDF_FAILD_TO_ALLOC_MEM, HPDF_NOERROR);
     return ptr;
 }
 
 void
-HPDF_FreeMem  (HPDF_MMgr  mmgr,
-               void       *aptr)
+HPDF_FreeMem(HPDF_MMgr mmgr, void *aptr)
 {
-    if (!aptr)
-        return;
-
-    if (!mmgr->mpool) {
-        HPDF_PTRACE(("-%p mmgr-free-mem\n", aptr));
-        mmgr->free_fn(aptr);
-
-#ifdef HPDF_MEM_DEBUG
-        mmgr->free_cnt++;
-#endif
-    }
-
-    return;
+    if (aptr)
+        free(aptr);
+    (void)mmgr;
 }
 
-static void * HPDF_STDCALL
-InternalGetMem  (HPDF_UINT  size)
-{
-    return HPDF_MALLOC (size);
-}
-
-static void HPDF_STDCALL
-InternalFreeMem  (void*  aptr)
-{
-    HPDF_FREE (aptr);
-}
-
-
diff --git a/src/hpdf_page_operator.c b/src/hpdf_page_operator.c
index 55ede68..6b19d7c 100644
--- a/src/hpdf_page_operator.c
+++ b/src/hpdf_page_operator.c
@@ -1461,7 +1461,7 @@ HPDF_Page_ShowText  (HPDF_Page    page,
     if (!attr->gstate->font)
         return HPDF_RaiseError (page->error, HPDF_PAGE_FONT_NOT_FOUND, 0);
 
-    tw = HPDF_Page_TextWidth (page, text);
+    tw = HPDF_Page_TextWidth (page, text, NULL);
     if (!tw)
         return ret;
 
@@ -1513,7 +1513,7 @@ HPDF_Page_ShowTextNextLine  (HPDF_Page    page,
     if (HPDF_Stream_WriteStr (attr->stream, " \'\012") != HPDF_OK)
         return HPDF_CheckError (page->error);
 
-    tw = HPDF_Page_TextWidth (page, text);
+    tw = HPDF_Page_TextWidth (page, text, NULL);
 
     /* calculate the reference point of text */
     attr->text_matrix.x -= attr->gstate->text_leading * attr->text_matrix.c;
@@ -1585,7 +1585,7 @@ HPDF_Page_ShowTextNextLineEx  (HPDF_Page    page,
     attr->gstate->word_space = word_space;
     attr->gstate->char_space = char_space;
 
-    tw = HPDF_Page_TextWidth (page, text);
+    tw = HPDF_Page_TextWidth (page, text, NULL);
 
     /* calculate the reference point of text */
     attr->text_matrix.x += attr->gstate->text_leading * attr->text_matrix.b;
@@ -2682,7 +2682,7 @@ InternalShowTextNextLine  (HPDF_Page    page,
     if ((ret = HPDF_Stream_WriteStr (attr->stream, " \'\012")) != HPDF_OK)
         return ret;
 
-    tw = HPDF_Page_TextWidth (page, text);
+    tw = HPDF_Page_TextWidth (page, text, NULL);
 
     /* calculate the reference point of text */
     attr->text_matrix.x -= attr->gstate->text_leading * attr->text_matrix.c;
diff --git a/src/hpdf_pages.c b/src/hpdf_pages.c
index d9004ab..212990d 100644
--- a/src/hpdf_pages.c
+++ b/src/hpdf_pages.c
@@ -1007,12 +1007,14 @@ AddAnnotation  (HPDF_Page        page,
 
 HPDF_EXPORT(HPDF_REAL)
 HPDF_Page_TextWidth  (HPDF_Page        page,
-                      const char      *text)
+                      const char      *text,
+		      const char *endptr)
 {
     HPDF_PageAttr attr;
     HPDF_TextWidth tw;
     HPDF_REAL ret = 0;
-    HPDF_UINT len = HPDF_StrLen(text, HPDF_LIMIT_MAX_STRING_LEN + 1);
+    HPDF_UINT len = endptr ? (endptr - text) + 1 :
+	    HPDF_StrLen(text, HPDF_LIMIT_MAX_STRING_LEN + 1);
 
     HPDF_PTRACE((" HPDF_Page_TextWidth\n"));
 
-- 
2.44.0

